<script lang="ts" setup>
import { computed, onErrorCaptured, ref } from 'vue';

import { useAntdDesignTokens } from '@vben/hooks';
import { preferences, usePreferences } from '@vben/preferences';

import { App, ConfigProvider, Spin, theme } from 'ant-design-vue';

import { antdLocale } from '#/locales';

defineOptions({ name: 'App' });

const { isDark } = usePreferences();
const { tokens } = useAntdDesignTokens();

// 捕获路由组件渲染错误，避免出现空白页面
const hasError = ref(false);
const errorMessage = ref('');
onErrorCaptured((err) => {
  hasError.value = true;
  errorMessage.value = (err as Error)?.message || '';
  // 阻止向上冒泡，交由本组件处理展示
  return false;
});

const tokenTheme = computed(() => {
  const algorithm = isDark.value
    ? [theme.darkAlgorithm]
    : [theme.defaultAlgorithm];

  // antd 紧凑模式算法
  if (preferences.app.compact) {
    algorithm.push(theme.compactAlgorithm);
  }

  return {
    algorithm,
    token: tokens,
  };
});
</script>

<template>
  <ConfigProvider :locale="antdLocale" :theme="tokenTheme">
    <App>
      <Suspense>
        <template #default>
          <RouterView />
        </template>
        <template #fallback>
          <div class="flex items-center justify-center w-full h-full py-16">
            <Spin size="large" tip="正在加载页面..." />
          </div>
        </template>
      </Suspense>
      <div v-if="hasError" class="p-6 text-center text-red-500">
        页面加载失败：{{ errorMessage || '未知错误' }}
      </div>
    </App>
  </ConfigProvider>
</template>

<style>
/* 调整侧边栏菜单项的内边距，增加间距可读性 */
:root {
  /* 顶级与普通菜单项的上下/左右内边距 */
  --menu-item-padding-y: 14px;
  --menu-item-padding-x: 12px;

  /* 弹出子菜单项的内边距（保持一致即可） */
  --menu-item-popup-padding-y: 14px;
  --menu-item-popup-padding-x: 12px;

  /* 折叠态菜单项内边距（左右为0以贴齐，但可按需调） */
  --menu-item-collapse-padding-y: 14px;
  --menu-item-collapse-padding-x: 0px;
}
</style>
